boost::any库是个很短小的类,它的主要作用是定义一个变量来存放任意类型的数据,我们首先来看下boost::any的使用方法。
boost::any最常见的用法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| #include <iostream> #include <list> #include <boost/any.hpp> typedef std::list<boost::any> list_any; void fill_list(list_any& la) { la.push_back(10); la.push_back(std::string("glemontree")); } void show_list(list_any& la) { list_any::iterator it; boost::any anyone; for (it = la.begin; it!= la.end(); ++it) { anyone = *it; if (anyone.type() == typeid(int)) { std::cout << boost::any_cast<int>(*it) << std::endl; } else if (anyone.type() == typeid(std::string)) { std::cout << boost::any_cast<std::string>(*it).c_str() << std::endl; } } }
|
boost::any可以表示任意类型,因此list_any可以存放任意类型的对象,也正因为boost::any可以表示任意类型,因此用不了多态的特性,因为没有统一的接口,因此在show_list()函数中获取容器中的元素时需要判别元素的真正类型,这增加了程序员的负担。
boost::any源码
实现any的功能主要由三部分组成:
- any类
- 真正保存数据的holder类和其基类placeholder
- 获取真正数据的模板函数any_cast,类型转换的功能
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72
| #include <iostream> #include <list> #include <cassert> class any { public: class placeholder { public: virtual ~placeholder() { } public: virtual const std::type_info& type() const = 0; virtual placeholder* clone() const = 0; }; template<typename ValueType> class holder : public placeholder { public: holder(const ValueType& value): held(value) { } public: virtual const std::type_info& type() const { return typeid(ValueType); } virtual placeholder* clone() const { return new holder(held); } public: ValueType held; }; public: any(): content(NULL) { } template<typename ValueType> any(const ValueType& value): content(new holder<ValueType>(value)) { } any(const any& other): content(other.content ? other.content->clone() : 0) { } ~any() { if (NULL != content) { delete content; } } private: placeholder* content; template<typename ValueType> friend ValueType any_cast(const any* operand); public: const std::type_info& type() const { return content ? content->type() : typeif(void); } }; template<typename ValueType> ValueType any_cast(const any& operand) { assert(operand.type() == typeid(ValueType)); return static_cast<any::holder<ValueType>*>(operand.content)->held; }
|
参考资料